package com.owen.menu;

import com.owen.emuns.PdfTypeEnums;
import com.owen.service.AppService;
import com.owen.service.impl.AppServiceImpl;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.file.FileVisitOption;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.*;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.stream.Collectors;

public class AppMenu {

    private Scanner input = new Scanner(System.in);

    private AppService appService = new AppServiceImpl();

    /**
     * 首页
     */
    public void index() {
        List<String> options = new ArrayList<>();
        System.out.println("=========================程序启动完成=============================");
        System.out.println("1. 合并pdf操作");
        options.add("1");
        System.out.println("2. 统计Excel操作");
        options.add("2");
        System.out.println("3. 处理二维码PDF");
        options.add("3");
        System.out.println("4. 处理二维码PDF（一页切三页）");
        options.add("4");
        System.out.println("5. 扫描Excel对颜色添加西班牙语");
        options.add("5");
        System.out.println("6. 退出");
        options.add("6");
        options.add("exit");
        System.out.print("请选择：");
        String option = input.next();
        while (!options.contains(option)) {
            System.out.print("输入有误，请重新输入:");
            option = input.next();
        }
        switch (option) {
            case "1":
                mergePdf();
                break;
            case "2":
                statisticsExcel();
                break;
            case "3":
                qrCode();
                break;
            case "4":
                oneCuttingThreePdf();
                break;
            case "5":
                excelColorSpain();
                break;
            case "exit":
            case "6":
                System.out.println("再见！");
                System.exit(0);
                break;

        }
        // 回调到自身
        index();

    }

    /**
     * 合并pdf
     */
    public void mergePdf() {
        System.out.print("请填写pdf文件所在位置：");
        String pathNext = input.next();
        Path path = Paths.get(pathNext);
        if (!Files.exists(path)) {
            System.out.println("文件夹不存在");
            return;
        }
        List<Path> pdfPaths = new ArrayList<>();
        try {
            Files.walk(path, 1, FileVisitOption.FOLLOW_LINKS).forEach(p -> {
                File file = p.toFile();
                if (file.isFile()) {
                    if (p.toString().toLowerCase(Locale.ROOT).endsWith(".pdf")) {
                        pdfPaths.add(p);
                    }
                }
            });
        } catch (IOException e) {
            e.printStackTrace();
        }

        if (pdfPaths.isEmpty()) {
            System.out.println("未找到pdf文件");
            return;
        }
        int sortCount = 0;
        String ynSort = "";
        List<String> indexs = new ArrayList<>();
        if (pdfPaths.size() > 1) {
            do {
                if (sortCount < 1) {
                    for (int i = 1; i <= pdfPaths.size(); i++)
                        indexs.add(String.valueOf(i));
                    System.out.println("====================pdf排序如下：");
                } else {
                    System.out.printf("请输入需要排序的坐标[%s-%s]：", 1, pdfPaths.size());
                    String indexStr = input.next();
                    while (!indexs.contains(indexStr)) {
                        System.out.printf("输入错误，请重新输入需要排序的坐标[%s-%s]：", 1, pdfPaths.size());
                        indexStr = input.next();
                    }

                    System.out.printf("请输入需要排序到第几位[%s-%s]：", 1, pdfPaths.size());
                    String sortStr = input.next();
                    while (!indexs.contains(sortStr)) {
                        System.out.printf("输入错误，请重新输入需要排序到第几位[%s-%s]：", 1, pdfPaths.size());
                        sortStr = input.next();
                    }
                    int index = Integer.parseInt(indexStr);
                    int sort = Integer.parseInt(sortStr);

                    if (index < sort) {
                        for (int i = index - 1; i < sort - 1; i++) {
                            Path path1 = pdfPaths.get(i);
                            Path path2 = pdfPaths.get(i + 1);
                            pdfPaths.set(i, path2);
                            pdfPaths.set(i + 1, path1);
                        }
                    } else {
                        for (int i = index - 1; i > sort - 1; i--) {
                            Path path1 = pdfPaths.get(i);
                            Path path2 = pdfPaths.get(i - 1);
                            pdfPaths.set(i, path2);
                            pdfPaths.set(i - 1, path1);
                        }
                    }
                    System.out.printf("第%s次排后，顺序如下：%n", sortCount);
                }
                sortCount++;
                for (int i = 0; i < pdfPaths.size(); i++) {
                    Path pdfPath = pdfPaths.get(i);
                    Path fileName = pdfPath.getFileName();
                    System.out.printf("[%s]  [%s]%n", (i + 1), fileName);
                }
                System.out.println("====================");
                System.out.print("是否需要手动排序（y：进行排序；其他：执行pdf转换）：");
                ynSort = input.next();
            } while ("y".equalsIgnoreCase(ynSort));
        }

        try {
            List<String> pdfTypes = new ArrayList<>();
            System.out.println("请选择pdf类型");
            PdfTypeEnums[] values = PdfTypeEnums.values();
            for (PdfTypeEnums value : values) {
                System.out.printf("%s. %s PDF%n", value.getCode(), value.getMsg());
                pdfTypes.add(value.getCode());
            }
            System.out.print("请选择：");
            String pyfType = input.next();
            while (!pdfTypes.contains(pyfType)) {
                System.out.print("选择有误，请重新选择：");
                pyfType = input.next();
            }
            PdfTypeEnums pdfTypeEnums = PdfTypeEnums.getPdfTypeEnums(pyfType);

            System.out.println("正在处理，请稍后...");
            String pathStr = appService.splitPageOneMergePDF(pdfPaths, pathNext, pdfTypeEnums);
            System.out.printf("处理完成，请打开该文件查看%s%n", pathStr);
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * 统计Excel
     */
    public void statisticsExcel() {
        System.out.print("请输入excel路径：");
        String excelPath = input.next();
        if (!excelPath.toLowerCase().endsWith(".xls") && !excelPath.toLowerCase().endsWith(".xlsx")) {
            System.out.println("请录入正确的excel文件路径");
            return;
        }
        if (!Files.exists(Paths.get(excelPath))) {
            System.out.println("您录入的excel文件不存在");
            return;
        }

        // 读取“订单内容”列数据
        List<String> orders = appService.readExcelByHead(excelPath, "订单内容");

        // 多空格容错
        for (int i = 0; i < orders.size(); i++) {
            if (orders.get(i).contains("  ")) {
                String order = orders.get(i);
                while (order.contains("  ")) {
                    order = order.replace("  ", " ");
                }
                orders.set(i, order);
            }
        }

        // 去重
        List<String> qcOrders = orders.stream().distinct().collect(Collectors.toList());

        // 组
        Set<String> groups = new LinkedHashSet<>();

        // 统计好将要导出的数据
        Map<String, String> statisticsMap = new HashMap<>();
        qcOrders.forEach(q -> {
            int endIndex = q.lastIndexOf(" ") == -1 ? q.length() : q.lastIndexOf(" ");
            String substring = q.substring(0, endIndex);

            String lastSubstring = substring.substring(substring.lastIndexOf(" ") + 1);

            String number = "0123456789";
            String c = String.valueOf(lastSubstring.charAt(0));

            if (number.contains(c)) {
                endIndex = substring.lastIndexOf(" ") == -1 ? substring.length() : substring.lastIndexOf(" ");
                substring = substring.substring(0, endIndex);
            }

            boolean b = true;
            for (String group : groups) {
                if (group.contains(substring)) {
                    b = false;
                }
            }

            if (b) {
                groups.add(substring);
            }

            // 统计个数
            int frequency = Collections.frequency(orders, q);
            statisticsMap.put(q, String.valueOf(frequency));
        });

        List<String> setRemove = new ArrayList<>();
        for (String set : groups) {
            int i = 0;
            for (String s : groups) {
                if (s.contains(set)) {
                    i++;
                }
            }
            if (i >= 2) {
                setRemove.add(set);
            }
        }

        for (String s : setRemove) {
            groups.remove(s);
        }

        String outPath = excelPath.substring(0, excelPath.lastIndexOf("\\") + 1) + "export\\";
        File outFile = new File(outPath);
        if (!outFile.exists()) {
            outFile.mkdirs();
        }
        String outExcel = outPath + UUID.randomUUID().toString() + ".xlsx";

        // 创建一个新的Excel工作簿
        Workbook workbook = new XSSFWorkbook();

        // 在工作簿中创建一个新的表格
        Sheet sheet = workbook.createSheet();

        sheet.setColumnWidth(0, 12000);

        // 创建行（Row）
        Row row = sheet.createRow(0);

        // 写入表头信息
        Cell cell00 = row.createCell(0);
        cell00.setCellValue("订单内容");
        Cell cell01 = row.createCell(1);
        cell01.setCellValue("数量");

        boolean kh = false;

        AtomicInteger rowIndex = new AtomicInteger(1);
        for (String group : groups) {
            statisticsMap.forEach((k, v) -> {
                if (k.startsWith(group) && v != null) {
                    Row row1 = sheet.createRow(rowIndex.get());
                    row1.createCell(0).setCellValue(k);
                    row1.createCell(1).setCellValue(v);
                    rowIndex.set(rowIndex.get() + 1);
                    statisticsMap.put(k, null);
                }
            });
            if (group.contains("保护膜") || group.contains("保护壳")) {
                if (kh) {
                    rowIndex.set(rowIndex.get() + 1);
                }
                kh = true;
            } else {
                rowIndex.set(rowIndex.get() + 1);
            }
        }

        // 分组容错
        statisticsMap.forEach((k, v) -> {
            if (v != null) {
                Row row1 = sheet.createRow(rowIndex.get());
                row1.createCell(0).setCellValue(k);
                row1.createCell(1).setCellValue(v);
                rowIndex.set(rowIndex.get() + 1);
                statisticsMap.put(k, null);
            }
        });

        FileOutputStream outputStream = null;
        // 将工作簿写入文件
        try {
            outputStream = new FileOutputStream(outExcel);
            workbook.write(outputStream);

        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                if (outputStream != null) {
                    outputStream.close();
                }
                workbook.close();
            } catch (IOException e) {
                throw new RuntimeException(e);
            }
        }
        System.out.printf("统计完成，请打开[%s]文件查看。%n", outExcel);
    }

    /**
     * 二维码pdf处理
     */
    private void qrCode() {
        System.out.print("请填写二维码pdf文件所在位置：");
        String pathNext = input.next();
        Path path = Paths.get(pathNext);
        if (!Files.exists(path)) {
            System.out.println("文件夹不存在");
            return;
        }
        List<Path> pdfPaths = new ArrayList<>();
        try {
            Files.walk(path, 1, FileVisitOption.FOLLOW_LINKS).forEach(p -> {
                File file = p.toFile();
                if (file.isFile()) {
                    if (p.toString().toLowerCase(Locale.ROOT).endsWith(".pdf")) {
                        pdfPaths.add(p);
                    }
                }
            });
        } catch (IOException e) {
            e.printStackTrace();
        }

        if (pdfPaths.isEmpty()) {
            System.out.println("未找到pdf文件");
            return;
        }

        // 处理二维码qrcode PDF
        appService.qrcodePdf(pdfPaths, pathNext);
    }


    /**
     * PDF一页切割为三页
     */
    private void oneCuttingThreePdf() {
        System.out.print("请填写二维码pdf文件所在位置：");
        String pathNext = input.next();
        Path path = Paths.get(pathNext);
        if (!Files.exists(path)) {
            System.out.println("文件夹不存在");
            return;
        }
        List<Path> pdfPaths = new ArrayList<>();
        try {
            Files.walk(path, 1, FileVisitOption.FOLLOW_LINKS).forEach(p -> {
                File file = p.toFile();
                if (file.isFile()) {
                    if (p.toString().toLowerCase(Locale.ROOT).endsWith(".pdf")) {
                        pdfPaths.add(p);
                    }
                }
            });
        } catch (IOException e) {
            e.printStackTrace();
        }

        if (pdfPaths.isEmpty()) {
            System.out.println("未找到pdf文件");
            return;
        }
        // 处理二维码qrcode PDF
        appService.oneCuttingThreePdf(pdfPaths, pathNext);
    }



    /**
     * 扫描指定pdf，对该pdf中的颜色添加西班牙语
     * 即 灰色 -> 灰色（Gris）
     */
    public void excelColorSpain() {
        System.out.print("请输入excel路径：");
        String excelPath = input.next();
        if (!excelPath.toLowerCase().endsWith(".xls") && !excelPath.toLowerCase().endsWith(".xlsx")) {
            System.out.println("请录入正确的excel文件路径");
            return;
        }
        if (!Files.exists(Paths.get(excelPath))) {
            System.out.println("您录入的excel文件不存在");
            return;
        }
        // 对录入的Excel做添加西班牙语处理
        appService.excelColorSpain(excelPath);

    }

}
